﻿<?xml version="1.0" encoding="utf-8"?>
<blog root-url="/CS21/blogs/p/default.aspx"
      date-created="2006-09-05T18:22:10"
      xmlns="http://www.blogml.com/2006/09/BlogML"
      xmlns:xs="http://www.w3.org/2001/XMLSchema">
  <title type="text"><![CDATA[BlogML 2.0 Sample Blog]]></title>
  <sub-title type="text"><![CDATA[This is a sample blog content for BlogML 2.0]]></sub-title>
  <authors>
    <author id="2100"
            date-created="2006-08-10T08:44:35"
            date-modified="2006-09-04T13:46:38"
            approved="true"
            email="someone@blogml.com">
      <title type="text"><![CDATA[admin]]></title>
    </author>
  </authors>
  <extended-properties>
    <property name="CommentModeration"
              value="Anonymous" />
    <property name="SendTrackback"
              value="Yes" />
  </extended-properties>
  <categories>
    <category id="1018"
              date-created="2006-09-05T17:54:58"
              date-modified="2006-09-05T17:54:58"
              approved="true"
              description="Sample Category 1"
              parentref="0">
      <title type="text"><![CDATA[Category 1]]></title>
    </category>
    <category id="1019"
              date-created="2006-09-05T17:54:59"
              date-modified="2006-09-05T17:54:59"
              approved="true"
              description="Sample Category 2"
              parentref="0">
      <title type="text"><![CDATA[Category 2]]></title>
    </category>
    <category id="1020"
              date-created="2006-09-05T17:55:00"
              date-modified="2006-09-05T17:55:00"
              approved="false"
              description="Sample Category 3"
              parentref="0">
      <title type="text"><![CDATA[Category 3]]></title>
    </category>
  </categories>
  <posts>
    <post id="34"
          date-created="2006-09-05T03:19:00"
          date-modified="2006-09-05T03:19:00"
          approved="true"
          post-url="/CS21/blogs/p/archive/2006/09/05/CS-Dev-Guide_3A00_-Send-Emails.aspx"
          type="normal"
          hasexcerpt="false"
          views="0">
      <title type="text"><![CDATA[CS Dev Guide: Send Emails]]></title>
      <content type="text"><![CDATA[<p>Any web application needs a way to send emails to different kinds of its users.&nbsp; This capability is provided in Community Server from early versions.&nbsp; Sending emails is one of easiest parts of Community Server development.</p><p>To send emails in Community Serve you have two options:&nbsp;using pre-defined email templates for some common situations&nbsp;or create an email manually.</p><p>First option is easy to implement.&nbsp; Community Server has provided several default templates for your emails and you can add your own templates via resource files as well.&nbsp; <em>CommunityServer.Components.Emails</em> namespace has many methods that get some parameters&nbsp;then create and send an email based on the template they have.</p><p>For example you can send a notification email to user to let him know his account is created.</p><div style="background: white none repeat scroll 0% 50%; font-size: 10pt; -moz-background-clip: -moz-initial; -moz-background-origin: -moz-initial; -moz-background-inline-policy: -moz-initial; color: black; font-family: courier new"><p style="margin: 0px"><span style="color: blue">private</span> <span style="color: blue">void</span> SendEmail(<span style="color: blue">string</span> username, <span style="color: blue">string</span> password</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; , <span style="color: blue">string</span> email)</p><p style="margin: 0px">{</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">User</span> user = <span style="color: blue">new</span> <span style="color: teal">User</span>();</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; user.Username = username;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; user.Password = password;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; user.Email = email;</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">Emails</span>.UserCreate(user, password);</p><p style="margin: 0px">}</p></div><p>These methods add emails to queue automatically.&nbsp; You can use <em>Emails.SendQueuedEmails()</em> method to send all queued emails to recipients.&nbsp; This method takes three parameters: an integer value for failure interval, an integer value that specifies the maximum number of tries of sending process&nbsp;failed and a <em>SiteSettings</em> object.</p><div style="background: white none repeat scroll 0% 50%; font-size: 10pt; -moz-background-clip: -moz-initial; -moz-background-origin: -moz-initial; -moz-background-inline-policy: -moz-initial; color: black; font-family: courier new"><p style="margin: 0px"><span style="color: blue">private</span> <span style="color: blue">void</span> SendQueuedEmails()</p><p style="margin: 0px">{</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">Emails</span>.SendQueuedEmails(5, 5,</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: teal">CSContext</span>.Current.SiteSettings);</p><p style="margin: 0px">}</p></div><p>Second option to send emails is&nbsp;manual option.&nbsp; This is&nbsp;useful when you want to send an email but it doesn&#39;t fit to Community Server pre-defined templates.</p><p>This option is very similar to sending emails in ASP.NET 1.x.&nbsp; You need to create an instance of System.Web.Mail.MailMessage object, set its appropriate properties and add it to emails queue using Community Server APIs.&nbsp; You know MailMessage object is obsolete in ASP.NET 2.0 but Community Server accepts old objects to be able to work under ASP.NET 1.1.&nbsp; If you need more information about sending emails in ASP.NET 2.0, read my post about my SMTP component, Gopi, from <a href="http://nayyeri.net/archive/2006/05/20/Gopi-_2D00_-SMTP-component-for-.NET-2.0.aspx">here</a>.</p><p>Here is a sample of how to create a new MailMessage and add it to emails queue.</p><div style="background: white none repeat scroll 0% 50%; font-size: 10pt; -moz-background-clip: -moz-initial; -moz-background-origin: -moz-initial; -moz-background-inline-policy: -moz-initial; color: black; font-family: courier new"><p style="margin: 0px"><span style="color: blue">private</span> <span style="color: blue">void</span> SendEmailManually()</p><p style="margin: 0px">{</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">MailMessage</span> mail = <span style="color: blue">new</span> <span style="color: teal">MailMessage</span>();</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; mail.From = <span style="color: maroon">&quot;sender@server.com&quot;</span>;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; mail.To = <span style="color: maroon">&quot;receiver@server.com&quot;</span>;</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; mail.Priority = <span style="color: teal">MailPriority</span>.Normal;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; mail.BodyFormat = <span style="color: teal">MailFormat</span>.Text;</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; mail.Body = <span style="color: maroon">&quot;Long Live Community Server!&quot;</span>;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; mail.Subject = <span style="color: maroon">&quot;Test Email&quot;</span>;</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">EmailQueueProvider</span>.Instance().QueueEmail(mail);</p><p style="margin: 0px">}</p></div><p>You saw I used <em>EmailQueueProvider.Instance().QueueEmail()</em> method to add my email to queue.&nbsp; You can use <em>EmailQueueProvider.Instance()</em> object to deal with emails queue in Community Server.&nbsp; For instance you can remove an email from emails queue by passing its Guid to <em>EmailQueueProvider.Instance().DeleteQueuedEmail()</em> method.</p><div style="background: white none repeat scroll 0% 50%; font-size: 10pt; -moz-background-clip: -moz-initial; -moz-background-origin: -moz-initial; -moz-background-inline-policy: -moz-initial; color: black; font-family: courier new"><p style="margin: 0px"><span style="color: blue">private</span> <span style="color: blue">void</span> DealWithEmails()</p><p style="margin: 0px">{</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">EmailQueueProvider</span>.Instance()</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; .DeleteQueuedEmail(<span style="color: teal">Guid</span>.NewGuid());&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; </p><p style="margin: 0px">}</p></div><p><strong>Now playing: </strong>Modern Talking - You are not alone</p>]]></content>
      <post-name type="text"><![CDATA[CS Dev Guide: Send Emails]]></post-name>
      <categories>
        <category ref="1018" />
      </categories>
      <comments>
        <comment id="35"
                 date-created="2006-09-05T11:36:50"
                 date-modified="2006-09-05T11:36:50"
                 approved="false"
                 user-name="Phil Haack"
                 user-url="http://haacked.com">
          <title type="text"><![CDATA[re: CS Dev Guide: Send Emails]]></title>
          <content type="text"><![CDATA[Another test comment.]]></content>
        </comment>
      </comments>
      <authors>
        <author ref="2100" />
      </authors>
    </post>
    <post id="36"
          date-created="2006-09-05T03:20:00"
          date-modified="2006-09-05T03:20:00"
          approved="true"
          post-url="/CS21/blogs/p/archive/2006/09/05/Asynchronous-command-execution-in-.NET-2.0.aspx"
          type="normal"
          hasexcerpt="false"
          views="0">
      <title type="text"><![CDATA[Asynchronous command execution in .NET 2.0]]></title>
      <content type="text"><![CDATA[<p>Asynchronous execution of commands&nbsp;was one of great new features in ADO.NET 2.0.&nbsp; The ability to execute commands that take long time to&nbsp;execute&nbsp;asynchronously is very helpful for developers.</p><p>The process of executing a command asynchronously&nbsp;is very simple and easy and I talk about it in this post.</p><h3>Database</h3><p>Before anything I create&nbsp;two stored procedures for SQL Server Northwind sample database&nbsp;to&nbsp;have a final stored procedure that takes time to execute.</p><p>First&nbsp;I create a stored procedure, SelectOrders,&nbsp;to select all orders from Orders table.</p><div style="font-size: 10pt; background: white 0% 50%; color: black; font-family: courier new; moz-background-clip: -moz-initial; moz-background-origin: -moz-initial; moz-background-inline-policy: -moz-initial"><p style="margin: 0px"><span style="color: blue">CREATE PROCEDURE </span>dbo.SelectOrders</p><p style="margin: 0px"><span style="color: blue">AS</span></p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">SELECT </span>* <span style="color: blue">FROM </span>dbo.Orders</p></div><p>Now it&#39;s time to create a stored procedure which takes time to execute.&nbsp; To write this stored procedure (MyStoredProcedure)&nbsp;I use new&nbsp;<a href="http://msdn2.microsoft.com/en-us/library/ms187331.aspx">WAITFOR</a>&nbsp;statement&nbsp;in SQL Server 2005 to make a five seconds delay in my stored procedure before executing SelectOrders procedure.</p><div style="font-size: 10pt; background: white 0% 50%; color: black; font-family: courier new; moz-background-clip: -moz-initial; moz-background-origin: -moz-initial; moz-background-inline-policy: -moz-initial"><p style="margin: 0px"><span style="color: blue">CREATE PROCEDURE </span>dbo.MyStoredProcedure </p><p style="margin: 0px"><span style="color: blue">AS</span></p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">WAITFOR </span>DELAY <span style="color: maroon">&#39;00:00:05&#39;</span></p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">EXEC </span>dbo.SelectOrders</p></div><h3>Executing Command</h3><p>There are three new methods for command objects in ADO.NET 2.0 which enable the&nbsp;ability to execute them asynchronously: BeginExecuteReader(), BeginExecuteNonQuery() and BeingExecuteXmlReader().</p><p>First one will be used for my sample.&nbsp; What I want is to get the list of orders via MyStoredProcedure and show them in a Windows Form GridView control.</p><p>I create a SqlConnection and SqlCommand to fetch my data&nbsp;and pass my connection string to SqlConnection object.&nbsp; Note that&nbsp;I&nbsp;add &quot;asyn=true;&quot; or &quot;Asynchronous Processing=true;&quot; to&nbsp;my connection string to enable asynchronous execution for&nbsp;my commands.&nbsp; If I don&#39;t add one of these strings, will get an error with&nbsp;following description when I want to call BeginExecuteReader() method:</p><p><em>This command requires an asynchronous connection. Set &quot;Asynchronous Processing=true&quot; in the connection string.</em></p><p>After opening a connection to database, I call BeginExecuteReader() by passing a delegate of my main logic method for asynchronous execution, my SqlCommand object and a CommandBehaviour enumeration to close the connection to database after finishing the execution automatically.</p><div style="font-size: 10pt; background: white 0% 50%; color: black; font-family: courier new; moz-background-clip: -moz-initial; moz-background-origin: -moz-initial; moz-background-inline-policy: -moz-initial"><p style="margin: 0px"><span style="color: blue">private</span> <span style="color: blue">void</span> Execute(<span style="color: blue">string</span> connectionstring)</p><p style="margin: 0px">{</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">SqlConnection</span> connection =</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">new</span> <span style="color: teal">SqlConnection</span>(connectionstring + <span style="color: maroon">&quot;async=true;&quot;</span>);</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">SqlCommand</span> command = </p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">new</span> <span style="color: teal">SqlCommand</span>(<span style="color: maroon">&quot;MyStoredProcedure&quot;</span>, connection);</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; command.CommandType = <span style="color: teal">CommandType</span>.StoredProcedure;</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; connection.Open();</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; command.BeginExecuteReader(Asynchronous, command,</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: teal">CommandBehavior</span>.CloseConnection);</p><p style="margin: 0px">}</p></div><p>Now I want to work on main logic for my command execution.&nbsp; I use Asynchronous()&nbsp;method to do this.&nbsp; This method takes one argument of IAsyncResult type.&nbsp; I convert AsyncState property of this parameter to a SqlCommand then create a SqlDataReader and set it to appropriate value&nbsp;via the&nbsp;SqlCommand I created&nbsp;and finally load the data of this SqlDataReader to a DataTable and pass this DataTable through a delegate to another method.</p><div style="font-size: 10pt; background: white 0% 50%; color: black; font-family: courier new; moz-background-clip: -moz-initial; moz-background-origin: -moz-initial; moz-background-inline-policy: -moz-initial"><p style="margin: 0px"><span style="color: blue">private</span> <span style="color: blue">void</span> Asynchronous(<span style="color: teal">IAsyncResult</span> asyncResult)</p><p style="margin: 0px">{</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">SqlCommand</span> command = </p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; asyncResult.AsyncState <span style="color: blue">as</span> <span style="color: teal">SqlCommand</span>;</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">SqlDataReader</span> reader;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; reader = command.EndExecuteReader(asyncResult);</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">DataTable</span> table = <span style="color: blue">new</span> <span style="color: teal">DataTable</span>();</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; table.Load(reader);</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; reader.Close();</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; Invoke(<span style="color: blue">new</span> <span style="color: teal">MyBindDelegate</span>(MyBind), table);</p><p style="margin: 0px">}</p></div><p>Below&nbsp;is latest bits of my sample code to define a MyBindDelegate delegate and MyBind() method to bind my DataTable to GridView control.</p><div style="font-size: 10pt; background: white 0% 50%; color: black; font-family: courier new; moz-background-clip: -moz-initial; moz-background-origin: -moz-initial; moz-background-inline-policy: -moz-initial"><p style="margin: 0px"><span style="color: blue">private</span> <span style="color: blue">delegate</span> <span style="color: blue">void</span> <span style="color: teal">MyBindDelegate</span>(<span style="color: teal">DataTable</span> table);</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px"><span style="color: blue">private</span> <span style="color: blue">void</span> MyBind(<span style="color: teal">DataTable</span> table)</p><p style="margin: 0px">{</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; GridView.DataSource = table;</p><p style="margin: 0px">}</p></div><p>But why I used this delegate to bind my&nbsp;data to GridView control?</p><p>.NET uses threading to accomplish asynchronous execution of commands so I used a delegate to move my Asynchronous() method to a new thread and I must do same and go back to first thread to bind my data to GridView at the end because GridView is located on another thread and can&#39;t be accessed within my new asynchronous thread.</p><p>Sample Windows Form application has been attached to this post.</p>]]></content>
      <post-name type="text"><![CDATA[Asynchronous command execution in .NET 2.0]]></post-name>
      <categories>
        <category ref="1018" />
      </categories>
      <comments>
        <comment id="37"
                 date-created="2006-09-05T11:29:54"
                 date-modified="2006-09-05T11:29:54"
                 approved="true"
                 user-name="admin"
                 user-url="http://nayyeri.net">
          <title type="text"><![CDATA[re: Asynchronous command execution in .NET 2.0]]></title>
          <content type="text"><![CDATA[I'm commenting for you!]]></content>
        </comment>
        <comment id="38"
                 date-created="2006-09-05T11:35:54"
                 date-modified="2006-09-05T11:35:54"
                 approved="true"
                 user-name="Darren Neimke"
                 user-url="http://markitup.com">
          <title type="text"><![CDATA[re: Asynchronous command execution in .NET 2.0]]></title>
          <content type="text"><![CDATA[A sample comment.]]></content>
        </comment>
      </comments>
      <authors>
        <author ref="2100" />
      </authors>
    </post>
    <post id="39"
          date-created="2006-09-05T03:22:00"
          date-modified="2006-09-05T03:22:00"
          approved="true"
          post-url="/CS21/blogs/p/archive/2006/09/05/FeedBurner-APIs-component-for-.NET-2.0.aspx"
          type="normal"
          hasexcerpt="false"
          views="1">
      <title type="text"><![CDATA[FeedBurner APIs component for .NET 2.0]]></title>
      <content type="text"><![CDATA[<p><img align="right" alt="FeedBurner" height="175" src="/misc/FeedBurnerAPIsversion1.0for.NET2.0_76F2/flamocon_175h17.gif" width="166" /> Some ages ago, when new&nbsp;<a href="http://www.feedburner.com">FeedBurner</a>&nbsp;site had been launched,&nbsp;I <a href="/archive/2005/09/29/More-about-FeedBurner.aspx">wanted</a> to write a component for FeedBurner APIs in .NET but we know &quot;Tomorrow is far away&quot;!</p><p>Now FeedBurner is a famous site and many users use their services around the web.&nbsp; When <a href="http://scottwater.com/">Scott Watermasysk</a> opened a feature item for Community Server to add external feed functionality to Community Server 2.1, I commented for him about category feeds and he replied back we should assume this feature just for main feeds.&nbsp; The necessity to have&nbsp;something to deal with FeedBurner APIs in some cases I&#39;ve seen,&nbsp;bit me to write a component for .NET community.&nbsp; Hope it helps developers to manipulate their feeds on FeedBurner on fly.</p><h3>Overview</h3><p><a href="http://www.feedburner.com/fb/a/developers;jsessionid=36AC8C7DF39B8896C9B78BCA404EA1A5.fb1">FeedBurner APIs</a> are rich enough to help every developer to deal with&nbsp;account feeds easily.&nbsp; FeedBurner is written with PHP and some APIs are a&nbsp;bit confusing specially when you must pass an XML file through query!!</p><p>However, I started writing this component to implement all FeedBurner APIs in .NET.&nbsp; I&#39;ve&nbsp;coded this component with C# 2.0 and used .NET 2.0 new features in many parts so it&#39;s not possible to&nbsp;apply it&nbsp;in .NET 1.x.&nbsp; On the other hand as I used WebClient object to Get or Post to FeedBurner server, probably you can&#39;t use this component under medium trust level in ASP.NET 2.0.</p><p>Most of the code implementation is around XML manipulation&nbsp;and reading the source code can be a good practice for those who want to learn more about XML in .NET.&nbsp; Talking about source code is out of scope of this blog post and I just&nbsp;show how can you use this component.&nbsp; You can view the source code from download package to find more about it.</p><p>This component throws appropriate exceptions for any pre-defined exception on FeedBurner and returns exception messages from what FeedBurner provides.&nbsp; List of some standard FeedBurner errors can be found <a href="http://www.feedburner.com/fb/a/developers/feedapi#Standard_Error_Responses">here</a>.</p><h3>How to use</h3><p>My component has self explanatory classes, objects and methods.&nbsp; To make things clear I give some samples in this post.</p><p>To work with my component, you need to create an instance of User object and set its username and password via constructor or its properties.&nbsp; Although it&#39;s not necessary to create a User object to use my component but I recommend it because it saves you from passing credentials via each and every operation.</p><div style="font-size: 10pt; background: white 0% 50%; color: black; font-family: courier new; moz-background-clip: -moz-initial; moz-background-origin: -moz-initial; moz-background-inline-policy: -moz-initial"><p style="margin: 0px"><span style="color: green">// Create a user and set its credentials via constructor</span></p><p style="margin: 0px"><span style="color: teal">User</span> user = <span style="color: blue">new</span> <span style="color: teal">User</span>(<span style="color: maroon">&quot;Username&quot;</span>, <span style="color: maroon">&quot;Password&quot;</span>);</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px"><span style="color: green">// Create a user and set its properties</span></p><p style="margin: 0px"><span style="color: teal">User</span> user2 = <span style="color: blue">new</span> <span style="color: teal">User</span>();</p><p style="margin: 0px">user2.Username = <span style="color: maroon">&quot;Username&quot;</span>;</p><p style="margin: 0px">user2.Password = <span style="color: maroon">&quot;Password&quot;</span>;</p></div><p>All six operations that my component supports have several overloads to get a Feed object or&nbsp;feed ID and feed Uri together.</p><p>To add a new feed, you should provide all properties for a Feed object after creating a new instance but leave the ID as null (although if you set it, no problem will occur) and call one of Feeds.Add() method overloads.&nbsp; Result of this method is a Feed object but it just has three properties available: ID, Title and Uri.</p><div style="font-size: 10pt; background: white 0% 50%; color: black; font-family: courier new; moz-background-clip: -moz-initial; moz-background-origin: -moz-initial; moz-background-inline-policy: -moz-initial"><p style="margin: 0px"><span style="color: teal">Feed</span> feed = <span style="color: blue">new</span> <span style="color: teal">Feed</span>();</p><p style="margin: 0px">feed.Title =</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: maroon">&quot;Keyvan Nayyeri&#39;s posts about .NET&quot;</span>;</p><p style="margin: 0px">feed.Uri = <span style="color: maroon">&quot;KeyvanNayyeri/DotNet&quot;</span>;</p><p style="margin: 0px">feed.Url = </p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: maroon">&quot;http://nayyeri.net/rss.aspx?Tags=.NET&amp;AndTags=1&quot;</span>;</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px"><span style="color: teal">Service</span> service = <span style="color: blue">new</span> <span style="color: teal">Service</span>(<span style="color: maroon">&quot;BrowserFriendly&quot;</span>);</p><p style="margin: 0px">service.Parameters.Add(<span style="color: maroon">&quot;style&quot;</span>, <span style="color: maroon">&quot;clear&quot;</span>);</p><p style="margin: 0px">service.Parameters.Add(<span style="color: maroon">&quot;message&quot;</span>, <span style="color: blue">null</span>);</p><p style="margin: 0px">feed.Services.Add(service);</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px"><span style="color: teal">Feed</span> result = <span style="color: teal">Feeds</span>.Add(user, feed);&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp; </p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px"><span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;ID: &quot;</span> + result.ID.ToString());</p><p style="margin: 0px"><span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;Uri: &quot;</span> + result.Uri);</p><p style="margin: 0px"><span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;Title: &quot;</span> + result.Title);</p></div><p>The process for &nbsp;modifying a feed is very similar to add as feed&nbsp;by calling Feeds.Modify() method except that if you want to change the Uri of a feed, must provide its ID.</p><p>You can also simply get the list of defined feeds for a specific user by calling Feeds.Find() method.&nbsp;&nbsp;This method will return a List&lt;Feed&gt; but don&#39;t forget that Feed objects won&#39;t have all properties available as same as the result of Feeds.Add() or Feeds.Modify() methods.</p><div style="font-size: 10pt; background: white 0% 50%; color: black; font-family: courier new; moz-background-clip: -moz-initial; moz-background-origin: -moz-initial; moz-background-inline-policy: -moz-initial"><p style="margin: 0px"><span style="color: blue">foreach</span> (<span style="color: teal">Feed</span> feed <span style="color: blue">in</span> <span style="color: teal">Feeds</span>.Find(user))</p><p style="margin: 0px">{</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;ID: &quot;</span> + feed.ID.ToString());</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;Uri: &quot;</span> + feed.Uri);</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;Title: &quot;</span> + feed.Title);</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">Console</span>.WriteLine();</p><p style="margin: 0px">}</p></div><p>Also you can get all details of a specific feed by&nbsp;passing its ID, Uri or a Feed object that contains these properties to Feeds.Get() method.&nbsp; This method&nbsp;returns a Feed object with all properties available.</p><div style="font-size: 10pt; background: white 0% 50%; color: black; font-family: courier new; moz-background-clip: -moz-initial; moz-background-origin: -moz-initial; moz-background-inline-policy: -moz-initial"><p style="margin: 0px"><span style="color: teal">Feed</span> feed = <span style="color: teal">Feeds</span>.Get(user, <span style="color: maroon">&quot;KeyvanNayyeri/DotNet&quot;</span>);</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px"><span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;ID: &quot;</span> + feed.ID.ToString());</p><p style="margin: 0px"><span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;Uri: &quot;</span> + feed.Uri);</p><p style="margin: 0px"><span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;Title: &quot;</span> + feed.Title);</p><p style="margin: 0px"><span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;Url: &quot;</span> + feed.Url);</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px"><span style="color: blue">if</span> (feed.Services.Count &gt; 0)</p><p style="margin: 0px">{</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">foreach</span> (<span style="color: teal">Service</span> service <span style="color: blue">in</span> feed.Services)</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; {</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;&nbsp; (Service) Name: &quot;</span> </p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; + service.Name);</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">if</span> (service.Parameters.Count &gt; 0)</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; {</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">foreach</span> (<span style="color: teal">KeyValuePair</span>&lt;<span style="color: blue">string</span>, <span style="color: blue">string</span>&gt; </p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; parameter <span style="color: blue">in</span> service.Parameters)</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: teal">Console</span>.WriteLine</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; (<span style="color: maroon">&quot;&nbsp;&nbsp;&nbsp; &nbsp; (Parameter) Name: &quot;</span> +</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; parameter.Key + <span style="color: maroon">&quot; Value: &quot;</span> + </p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; parameter.Value);</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; }</p><p style="margin: 0px">&nbsp;&nbsp;&nbsp; }</p><p style="margin: 0px">}</p></div><p>To delete or resync a feed, you can call Feeds.Delete() or Feeds.Resync() methods.&nbsp; They don&#39;t return anything.</p><div style="font-size: 10pt; background: white 0% 50%; color: black; font-family: courier new; moz-background-clip: -moz-initial; moz-background-origin: -moz-initial; moz-background-inline-policy: -moz-initial"><p style="margin: 0px"><span style="color: teal">Feed</span> feed = <span style="color: blue">new</span> <span style="color: teal">Feed</span>();</p><p style="margin: 0px">feed.Uri = <span style="color: maroon">&quot;KeyvanNayyeri/DotNet&quot;</span>;</p><p style="margin: 0px">&nbsp;</p><p style="margin: 0px"><span style="color: teal">Feeds</span>.Delete(user, feed);</p><p style="margin: 0px"><span style="color: teal">Console</span>.WriteLine(<span style="color: maroon">&quot;Specific feed has been removed.&quot;</span>);</p></div><p>Note that some operations may take time to be shown on FeedBurner website.</p><p>I put a sample Windows Console application in download package to show how to use my component APIs.&nbsp; This is the output of my sample Console Application:</p><p><a href="/misc/FeedBurnerAPIsversion1.0for.NET2.0_76F2/FB14.jpg"><img alt="Output" border="0" height="227" src="/misc/FeedBurnerAPIsversion1.0for.NET2.0_76F2/FB1_thumb1.jpg" width="450" /></a></p><p>And this is what my feed looks like after adding it via APIs:</p><p><a href="/misc/FeedBurnerAPIsversion1.0for.NET2.0_76F2/FB29.jpg"><img alt="Adding a feed to FeedBurner via APIs" border="0" height="361" src="/misc/FeedBurnerAPIsversion1.0for.NET2.0_76F2/FB2_thumb5.jpg" width="380" /></a> </p><h3>Download</h3><p>FeedBurner APIs component for .NET 2.0 is available <a href="/files/folders/feedburner_api/entry2544.aspx">here</a> with source code.</p>]]></content>
      <post-name type="text"><![CDATA[FeedBurner APIs component for .NET 2.0]]></post-name>
      <categories>
        <category ref="1019" />
      </categories>
      <trackbacks>
        <trackback id="40"
                   date-created="2006-09-05T11:27:11"
                   date-modified="2006-09-05T11:27:11"
                   approved="true"
                   url="http://localhost/CS21RC1/archive/2006/09/05/18.aspx">
          <title type="text"><![CDATA[Give me a Trackback]]></title>
        </trackback>
      </trackbacks>
      <attachments>
        <attachment url="21486.jpg"
                    size="2995"
                    mime-type="image/jpeg"
                    embedded="true">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</attachment>
      </attachments>
      <authors>
        <author ref="2100" />
      </authors>
    </post>
    <post id="33"
          date-created="2006-09-05T11:08:00"
          date-modified="2006-09-05T11:08:00"
          approved="true"
          post-url="/CS21/blogs/p/pages/Write-Atomic-Transactions-in-.NET.aspx"
          type="article"
          hasexcerpt="false"
          views="0">
      <title type="text"><![CDATA[Write Atomic Transactions in .NET]]></title>
      <content type="text"><![CDATA[<p>ACID theory is familiar to many programmers.&nbsp; Those who work on Operating System design concern&nbsp;about it everyday.</p> <p>Most important aspect of ACID is Atomic transactions.&nbsp; But what&#39;s an Atomic transaction?&nbsp; The best way to describe it is a famous common example: a bank accounting system.</p> <p>Consider that bank A and bank B want to interact with someone&#39;s account on same time.&nbsp; Both banks&nbsp;want to withdraw from account and account has $10.00 currently.&nbsp; If bank A gets&nbsp;$7.00 and on same time bank B tries to get&nbsp;$5.00, what will happen?&nbsp; One of annoying situations is when both banks start transactions on same time.&nbsp; As they think there is $10.00 available in account, start their interaction but one of them&nbsp;finishes&nbsp;earlier and second one won&#39;t have enough money to get.</p> <p>This scenario is common for computer systems and you can see it many times in memory management, IO operations and database interactions.</p> <p>Atomic transactions&nbsp;are a way to avoid this problem.&nbsp; They simply lock on a transaction and don&#39;t let any other transaction to&nbsp;interact&nbsp;with same resource.&nbsp; If anything fails during the Atomic transaction, everything will&nbsp;return to the state before transaction&#39;s start.</p> <p>In this post I want to give a sample to write an Atomic transaction in .NET and test to see it in action.&nbsp; In this example I create a simple accounting system then in an Atomic transaction add values to&nbsp;an account and place a case to throw exceptions&nbsp;for some arguments to see what will happen if in an Atomic transaction something goes wrong.</p> <h3>Database</h3> <p>To write my sample, I create a simple table with three columns:</p> <ul> <li>id (int)  </li><li>Name (navarchar)  </li><li>Value (int)</li></ul> <p>Consider each row is an account in a bank.&nbsp; Now I create a stored procedure to&nbsp;Add a value to&nbsp;a specific account.</p> <div style="background: white none repeat scroll 0% 50%; font-size: 10pt; -moz-background-clip: -moz-initial; -moz-background-origin: -moz-initial; -moz-background-inline-policy: -moz-initial; color: black; font-family: courier new"> <p style="margin: 0px"><span style="color: green">/* Add a value to an account */</span></p> <p style="margin: 0px"><span style="color: blue">CREATE PROCEDURE </span>dbo.AddToAccount&nbsp;&nbsp;&nbsp; </p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; (</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; @id <span style="color: blue">int</span>,</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; @value <span style="color: blue">int</span></p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; )</p> <p style="margin: 0px"><span style="color: blue">AS</span></p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">UPDATE </span>dbo.MyTable</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">SET </span>Value = (Value + @value)</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">WHERE </span>id= @id</p></div> <p>To finish preparing my database, I add a sample account to my table.</p> <p><img src="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic17.jpg" alt="" width="320" height="85" /></p> <h3>Write Atomic Transaction</h3> <p><img src="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic015.jpg" alt="" width="160" height="371" align="right" /> Writing an Atomic transaction is easy in .NET.&nbsp; First I create a Class Library project then create a MyTransaction class to implement my logic in it.</p> <p>MyTransaction has a Transfer() method that gets the identifier of an account, the integer value to add to that account and database connection string.&nbsp; This method tries to add the value to the specific account in an Atomic transaction.&nbsp; I&#39;ll produce an exception in this transaction to show what will happen if value wasn&#39;t valid according to sample constraints.&nbsp; I throw this exception after successfully adding a value to an account.</p> <p>What&nbsp;I need to build my Class Library project is adding a reference to System.EnterpriseServices, inheriting my class from ServicesComponent base class and call ContextUtil.SetComplete() method at the end of my Atomic transaction.</p> <p>So&nbsp;initially my class looks like this:</p> <div style="background: white none repeat scroll 0% 50%; font-size: 10pt; -moz-background-clip: -moz-initial; -moz-background-origin: -moz-initial; -moz-background-inline-policy: -moz-initial; color: black; font-family: courier new"> <p style="margin: 0px"><span style="color: blue">using</span> System;</p> <p style="margin: 0px"><span style="color: blue">using</span> System.Collections.Generic;</p> <p style="margin: 0px"><span style="color: blue">using</span> System.Text;</p> <p style="margin: 0px"><span style="color: blue">using</span> System.EnterpriseServices;</p> <p style="margin: 0px"><span style="color: blue">using</span> System.Data;</p> <p style="margin: 0px"><span style="color: blue">using</span> System.Data.SqlClient;</p> <p style="margin: 0px">&nbsp;</p> <p style="margin: 0px"><span style="color: blue">namespace</span> AtomicTransactions</p> <p style="margin: 0px">{</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">public</span> <span style="color: blue">class</span> <span style="color: teal">MyTransaction</span>&nbsp; : <span style="color: teal">ServicedComponent</span></p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; {</p></div> <p>Note that&nbsp;I can&#39;t provide a public default constructor for this class because later I can&#39;t register it as COM+ component service.</p> <p>Below&nbsp;is the logic for&nbsp;Transaction() method.&nbsp; After adding the value to database, I check a constraint and throw an exception if value wasn&#39;t between 0 and 10.&nbsp; This is a sample constraint&nbsp;to show the result in test stages.</p> <div style="background: white none repeat scroll 0% 50%; font-size: 10pt; -moz-background-clip: -moz-initial; -moz-background-origin: -moz-initial; -moz-background-inline-policy: -moz-initial; color: black; font-family: courier new"> <p style="margin: 0px"><span style="color: blue">public</span> <span style="color: blue">void</span> Transfer(<span style="color: blue">int</span> accountID, <span style="color: blue">int</span> value,</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">string</span> connectionString)</p> <p style="margin: 0px">{</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">try</span></p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; {</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; AddValue(accountID, value, connectionString);</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">if</span> ((value &lt; 0) || (value &gt; 10))</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">throw</span> <span style="color: blue">new</span> </p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: teal">ArgumentException</span>(<span style="color: maroon">&quot;Value isn&#39;t valid!&quot;</span>);</p> <p style="margin: 0px">&nbsp;</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: green">// Atomic transaction ends here</span></p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: teal">ContextUtil</span>.SetComplete();</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; }</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">catch</span> (<span style="color: teal">Exception</span> ex)</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; {</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">throw</span> <span style="color: blue">new</span> <span style="color: teal">Exception</span></p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; (<span style="color: maroon">&quot;An error occurred in our transaction&quot;</span>);</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; }</p> <p style="margin: 0px">}</p></div> <p>Simple logic for AddValue() method is:</p> <div style="background: white none repeat scroll 0% 50%; font-size: 10pt; -moz-background-clip: -moz-initial; -moz-background-origin: -moz-initial; -moz-background-inline-policy: -moz-initial; color: black; font-family: courier new"> <p style="margin: 0px"><span style="color: blue">private</span> <span style="color: blue">void</span> AddValue(<span style="color: blue">int</span> id, <span style="color: blue">int</span> value, </p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">string</span> connectionString)</p> <p style="margin: 0px">{</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">try</span></p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; {</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">using</span> (<span style="color: teal">SqlConnection</span> connection =</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">new</span> <span style="color: teal">SqlConnection</span>(connectionString))</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; {</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: teal">SqlCommand</span> command = </p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">new</span> <span style="color: teal">SqlCommand</span>(<span style="color: maroon">&quot;AddToAccount&quot;</span>, connection);</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; command.CommandType = <span style="color: teal">CommandType</span>.StoredProcedure;</p> <p style="margin: 0px">&nbsp;</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; command.Parameters.AddWithValue(<span style="color: maroon">&quot;id&quot;</span>, id);</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; command.Parameters.AddWithValue(<span style="color: maroon">&quot;value&quot;</span>, value);</p> <p style="margin: 0px">&nbsp;</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; connection.Open();</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; command.ExecuteNonQuery();</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; }</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; }</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">catch</span> (<span style="color: teal">Exception</span> ex)</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; {</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">throw</span> ex;</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; }</p> <p style="margin: 0px">}</p></div> <h3>Register&nbsp;Component Service</h3> <p>After creating my simple class, I need to set its transaction behavior.&nbsp; I can do it via an attribute in my code (which I&#39;ll do) or via Component Services MMC snap-in.</p> <p>There are several options for TransactionOption enumerator but I choose RequiresNew to create a new transaction with my component.&nbsp; You can find more about other options on MSDN.&nbsp; I also set my ApplicationAccessControl for assembly attribute to true.</p> <div style="background: white none repeat scroll 0% 50%; font-size: 10pt; -moz-background-clip: -moz-initial; -moz-background-origin: -moz-initial; -moz-background-inline-policy: -moz-initial; color: black; font-family: courier new"> <p style="margin: 0px"><span style="color: blue">namespace</span> AtomicTransactions</p> <p style="margin: 0px">{&nbsp;&nbsp;&nbsp; </p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; [assembly: <span style="color: teal">ApplicationAccessControl</span>(<span style="color: blue">true</span>)]</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; [<span style="color: teal">Transaction</span>(<span style="color: teal">TransactionOption</span>.RequiresNew)]</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">public</span> <span style="color: blue">class</span> <span style="color: teal">MyTransaction</span>&nbsp; : <span style="color: teal">ServicedComponent</span></p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; {</p></div> <p>Now I build my assembly but must make it COM Visible also&nbsp;create a&nbsp;strong name&nbsp;for this assembly.&nbsp; Finally I compile my Class Library and register it as a Component Service via Visual Studio command prompt:</p> <p><em>C:\Visual Studio 2005\Projects\AtomicTransactions\AtomicTransactions\bin\Debug&gt;regsvcs AtomicTransactions.dll</em></p> <p><a href="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic77.jpg"><img src="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic7_thumb1.jpg" border="0" alt="" width="380" height="284" /></a> </p> <h3>Test Application</h3> <p>To test my Atomic transaction, I write a Windows Form application&nbsp;that uses my Class Library.&nbsp; It simply gets the ID and value for an account and&nbsp;pass them to Transfer() method.&nbsp; This Windows Form application must have a reference to System.EnterpriseServices as well.</p> <p><img src="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic210.jpg" alt="" width="250" height="99" /> </p> <p>This is the event handler for my btnTransfer button:</p> <div style="background: white none repeat scroll 0% 50%; font-size: 10pt; -moz-background-clip: -moz-initial; -moz-background-origin: -moz-initial; -moz-background-inline-policy: -moz-initial; color: black; font-family: courier new"> <p style="margin: 0px"><span style="color: blue">private</span> <span style="color: blue">void</span> btnTransfer_Click(<span style="color: blue">object</span> sender, <span style="color: teal">EventArgs</span> e)</p> <p style="margin: 0px">{</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">MyTransaction</span> transaction = <span style="color: blue">new</span> <span style="color: teal">MyTransaction</span>();</p> <p style="margin: 0px">&nbsp;</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">try</span></p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; {</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; transaction.Transfer(</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: teal">Convert</span>.ToInt32(txtID.Text),</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: teal">Convert</span>.ToInt32(txtValue.Text),</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: maroon">&quot;Data Source=KEYVANNAYYERI;Initial &quot;</span></p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; + <span style="color: maroon">&quot;Catalog=AtomicTransaction;&quot;</span> </p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; + <span style="color: maroon">&quot;Integrated Security=True;Pooling=False&quot;</span>);</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; }</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: blue">catch</span> (<span style="color: teal">Exception</span> ex)</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; {</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <span style="color: blue">throw</span> ex;</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; }</p> <p style="margin: 0px">&nbsp;</p> <p style="margin: 0px">&nbsp;&nbsp;&nbsp; <span style="color: teal">MessageBox</span>.Show(<span style="color: maroon">&quot;Finished!&quot;</span>);</p> <p style="margin: 0px">}</p></div> <h3>Test Results</h3> <p>Now I run my application to test my component.&nbsp; But before doing this, I check current state of my database&nbsp;and Component Services Transaction Statistics:</p> <p><img src="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic113.jpg" alt="" width="320" height="87" />&nbsp;</p> <p><a href="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic314.jpg"><img src="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic3_thumb6.jpg" border="0" alt="" width="320" height="290" /></a> </p> <p>I run my application and&nbsp;give&nbsp;valid values (1 for ID and 5 for value) to it.&nbsp; Result is normal in database but look at Transaction Statistics.</p> <p><img src="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic44.jpg" alt="" width="320" height="88" /> &nbsp;</p> <p><a href="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic55.jpg"><img src="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic5_thumb3.jpg" border="0" alt="" width="320" height="290" /></a> </p> <p>Now I provide an invalid value, say 11, for my application to throw an exception in my Atomic transaction.&nbsp; Nothing will change in database but Transaction Statistics show an Aborted transaction.&nbsp; In normal form database must updated because value must be added to database before exception.</p> <p><img src="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic49.jpg" alt="" width="320" height="88" /> &nbsp;</p> <p><a href="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic64.jpg"><img src="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic6_thumb2.jpg" border="0" alt="" width="320" height="290" /></a> </p> <p>Note that an Atomic transaction can be applied to many kinds of transactions not only database transactions.&nbsp; For instance you can apply it to files.</p> <p><strong>Now playing:&nbsp;</strong>Pink Floyd - Lost For Words</p>]]></content>
      <post-name type="text"><![CDATA[Write Atomic Transactions in .NET]]></post-name>
      <categories>
        <category ref="1018" />
      </categories>
      <attachments>
        <attachment url="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic015.jpg"
                    mime-type="image/jpeg"
                    external-uri="http://nayyeri.net/misc/AtomicTransactionsin.NET_8E4/Atomic015.jpg"
                    embedded="false" />
      </attachments>
      <authors>
        <author ref="2100" />
      </authors>
    </post>
  </posts>
</blog>
